package com.xyoto.takeawayBusiness.service.impl;

import com.github.pagehelper.PageHelper;
import com.xyoto.takeawayBusiness.constant.CategoryStatus;
import com.xyoto.takeawayBusiness.constant.DataBasesOperationResult;
import com.xyoto.takeawayBusiness.dto.PageDTO;
import com.xyoto.takeawayBusiness.dto.SaveCategoryDTO;
import com.xyoto.takeawayBusiness.dto.UpdateCategoryDTO;
import com.xyoto.takeawayBusiness.entity.Category;
import com.xyoto.takeawayBusiness.entity.Shopping;
import com.xyoto.takeawayBusiness.entity.UserCache;
import com.xyoto.takeawayBusiness.enums.CategoryEnum;
import com.xyoto.takeawayBusiness.enums.CommonEnum;
import com.xyoto.takeawayBusiness.enums.OrderEnum;
import com.xyoto.takeawayBusiness.enums.ShoppingEnum;
import com.xyoto.takeawayBusiness.exception.ExceptionUtils;
import com.xyoto.takeawayBusiness.mapper.*;
import com.xyoto.takeawayBusiness.po.OrderShoppingPO;
import com.xyoto.takeawayBusiness.po.OrdersPO;
import com.xyoto.takeawayBusiness.po.ShoppingGoodPO;
import com.xyoto.takeawayBusiness.po.UserAddrPO;
import com.xyoto.takeawayBusiness.service.HomeService;
import com.xyoto.takeawayBusiness.utils.JudgeParamUtils;
import com.xyoto.takeawayBusiness.utils.PageUtils;
import com.xyoto.takeawayBusiness.utils.RedisUtils;
import com.xyoto.takeawayBusiness.utils.Result;
import com.xyoto.takeawayBusiness.vo.CategoryVO;
import com.xyoto.takeawayBusiness.vo.OrdersVO;
import com.xyoto.takeawayBusiness.vo.ShoppingVO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort.Order;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

@Service
@Slf4j
public class HomeServiceImpl implements HomeService {

    @Autowired
    private OrderMapper orderMapper;

    @Autowired
    private UserAddrMapper userAddrMapper;

    @Autowired
    private RedisUtils redisUtils;

    @Resource
    private HttpServletRequest request;

    @Autowired
    private CategoryMapper categoryMapper;

    @Autowired
    private ShoppingMapper shoppingMapper;

    @Autowired
    private ShoppingAttributeMapper shoppingAttributeMapper;

    @Autowired
    private ShoppingGoodsMapper shoppingGoodsMapper;

    /**
     * 获取商品详情
     * @param id
     * @return
     */
    @Override
    public Result getShopping(Integer id) {
        JudgeParamUtils.judgeIntegerParam(id, ShoppingEnum.SHOPPING_ERROR);

        // 查询商品信息
        ShoppingVO shoppingVo = shoppingMapper.getShoppingInfoById(id);
        if (Objects.isNull(shoppingVo)){
            return null;
        }
        // 查询商品规格、属性
        shoppingVo.setShoppingGoodsList(shoppingGoodsMapper.getShoppingGoods(shoppingVo.getId()));
        shoppingVo.setShoppingAttributeList(shoppingAttributeMapper.getShoppingAttribute(shoppingVo.getId()));
        return Result.success(shoppingVo);
    }

    /**
     * 分页查询新订单，处理中，退款单订单列表
     * @param pageDTO
     * @return
     */
    @Override
    public Result getOrderListByOrderType(PageDTO pageDTO, Integer orderType) {
        log.info("分页查询新订单，处理中，退款单订单列表开始");
        if (orderType == null || orderType <= 0){
            ExceptionUtils.error(OrderEnum.ORDER_TYPE_ERROR);
        }
        List<OrdersVO> ordersVOList = new ArrayList<>();
        PageHelper.startPage(pageDTO.getPageNum(), pageDTO.getPageSize());
        List<OrdersPO> ordersPoList = orderMapper.getOrderListByOrderType(orderType);
        if (ordersPoList.isEmpty()) {
            log.info("订单为空，查询失败");
            ExceptionUtils.error(OrderEnum.ORDER_LIST_IS_NULL);
        }
        for (OrdersPO ordersPo : ordersPoList) {
            OrdersVO ordersVO = new OrdersVO();
            BeanUtils.copyProperties(ordersPo, ordersVO);

            //通过订单id获取订单商品项
            List<OrderShoppingPO> orderShoppingPoList = orderMapper.getOrdersItems(ordersPo.getId());
            if (!orderShoppingPoList.isEmpty()) {
                //通过订单商品项商品id查询商品规格
                for (OrderShoppingPO orderShoppingPo : orderShoppingPoList) {
                    ShoppingGoodPO shoppingGoodPo = orderMapper.getShoppingGoods(orderShoppingPo.getShoppingId());
                    if (shoppingGoodPo != null) {
                        orderShoppingPo.setShoppingTotalPrice(shoppingGoodPo.getGoodsPrice() * orderShoppingPo.getCount());
                    }
                    orderShoppingPo.setShoppingGoodPo(shoppingGoodPo);
                }
                ordersVO.setOrderShoppingPoList(orderShoppingPoList);
            }
            //通过用户id查询用户默认地址
            UserAddrPO userAddrPo = userAddrMapper.searchUserDefaultAddrById(ordersPo.getUserAddrId());
            if (userAddrPo == null) {
                log.info("用户还没有地址");
            }
            ordersVO.setUserAddrPo(userAddrPo);
            ordersVOList.add(ordersVO);
        }
        log.info("分页查询订单列表成功");
        return Result.success(PageUtils.restPage(ordersPoList, ordersVOList));
    }

    /**
     * 接单打印
     * @return
     */
    @Override
    public Result orderReceiving(String orderId) {
        log.info("接单打印~~~");
        if (orderId == null || orderId.length() == 0){
            log.info("订单id异常");
            ExceptionUtils.error(OrderEnum.ORDER_ID_IS_NULL);
        }
        Integer status = orderMapper.orderReceiving(orderId);
        if (status == null || status == 0){
            log.info("修改订单失败");
            ExceptionUtils.error(OrderEnum.ORDER_UPDATE_FAILED);
        }

        // TODO  接单打印
        log.info("修改订单成功");
        return Result.success();
    }

    /**
     * 新增商品经营类别
     * @param saveCategoryDTO 新增商品经营类别DTO
     * @return
     */
    @Override
    public Result saveCategory(SaveCategoryDTO saveCategoryDTO) {

        UserCache redisUserMessage = redisUtils.getRedisUserMessage(request);
        log.info(redisUserMessage.getId() + " 正在进行操作");
        if (redisUserMessage.getId() != 1){
            ExceptionUtils.error(CommonEnum.REFUSE);
        }
        Short order = categoryMapper.getCategoryOrder();
        order = order == null ? 0 : order;
        Category category = new Category();
        category.setTitle(saveCategoryDTO.getTitle());
        category.setOrder(++order);

        log.info("执行新增商品经营类别");
        Integer saved = categoryMapper.saveCategory(category);
        if (saved == DataBasesOperationResult.ERROR){
            log.error("新增经营品类失败");
            ExceptionUtils.error(CategoryEnum.SAVE_CATEGORY_FAILED);
        }

        return Result.success();
    }

    /**
     * 获取经营品类列表
     * @return
     */
    @Override
    public Result getAllCategory() {

        log.info("查询经营品类列表");
        List<CategoryVO> list = categoryMapper.getCategoryList(CategoryStatus.OPEN);

        return Result.success(list);
    }

    /**
     * 修改经营品类
     * @param updateCategoryDTO 修改经营品类实体
     * @return
     */
    @Override
    public Result updateCategory(UpdateCategoryDTO updateCategoryDTO) {

        UserCache redisUserMessage = redisUtils.getRedisUserMessage(request);
        log.info(redisUserMessage.getId() + " 正在进行操作");
        if (redisUserMessage.getId() != 1){
            ExceptionUtils.error(CommonEnum.REFUSE);
        }
        Category category = new Category();
        BeanUtils.copyProperties(updateCategoryDTO,category);
        //判断是否存在相同的order
        Category category1 = categoryMapper.getCategoryOrderNums(category.getOrder());
        if (category1 != null && !category1.getId().equals(category.getId())){
            Short categoryOrder = categoryMapper.getCategoryOrder();
            category1.setOrder(++categoryOrder);
            log.info("进行相同的order进行更新");
            Integer update = categoryMapper.updateCategory(category1);
            if (update == DataBasesOperationResult.ERROR){
                ExceptionUtils.error(CategoryEnum.UPDATE_CATEGORY_FAILED);
            }
        }
        log.info("执行修改经营品类");
        Integer updateOrder = categoryMapper.updateCategory(category);
        if (updateOrder == DataBasesOperationResult.ERROR){
            log.error("修改经营品类失败");
            ExceptionUtils.error(CategoryEnum.UPDATE_CATEGORY_FAILED);
        }

        return Result.success();
    }
}
